#include <functional>
#include <iostream>
using namespace std;
// template <class T> 
// class function; // undefined;

// template <class Ret, class ...Args>
// class function<Ret(Args...)>;
// int main() {
//     return 0;
// }


// #include <iostream>
// #include <functional>
// using namespace std;
// int f(int a, int b) {
//     return a + b;
// }

// struct Functor {
//     public:
//         int operator() (int a, int b) {
//             return a + b;
//         }
// };

// class Plus {
//     public:
//         Plus(int n = 10) : _n(n) {}

//         static int plusi(int a, int b) {
//             return a + b;
//         }

//         double plusd(double a, double b) {
//             return (a + b) * _n;
//         }
//     private:
//         int _n;
// };

// int main() {
//     // 包装可调用对象
//     function<int(int, int)> f1 = f;
//     function<int(int, int)> f2 = Functor();
//     function<int(int, int)> f3 = [](int a, int b) {
//         return a + b;
//     };

//     cout << f1(1, 1) << endl;
//     cout << f2(1, 1) << endl;
//     cout << f3(1, 1) << endl;

//     // 包装静态成员函数
//     // 这里需要指定类域并且在前面加上&才能获取地址
//     function<int(int, int)> f4 = &Plus::plusi;
//     // function<int(int, int)> f4 = Plus::plusi; // 这里也可以没有&
//     cout << f4(1, 1) << endl;

//     // 包装普通成员函数
//     // 普通成员函数还有一个隐含的this指针，所以绑定的时候传入对象或是对象指针都是可以的
//     function<double(Plus*, double, double)> f5 = &Plus::plusd;
//     Plus pd;
//     cout << f5(&pd, 1.1, 1.1) << endl;

//     function<double(Plus, double, double)> f6 = &Plus::plusd;
//     cout << f6(pd, 1.1, 1.1) << endl;

//     function<double(Plus&&, double, double)> f7 = &Plus::plusd;
//     cout << f7(move(pd), 1.1, 1.1) << endl;
//     cout << f7(Plus(), 1.1, 1.1) << endl;
//     return 0;
// }

#include <iostream>
using namespace std;

template<class F, class T>
T func(F f, T t) {
    static int temp = 1;
    cout << "&temp: " << &temp << endl;
    return f(t);
}

int f(int x) {
    return x * 2;
}

struct Functor {
    int operator()(int x) {
        return x * 3;
    }
};

// int main() {
//     // 函数指针
//     cout << func(f, 2) << endl;
//     cout << "****************" << endl;

//     // 仿函数
//     cout << func(Functor(), 2) << endl;
//     cout << "****************" << endl;

//     // lambda表达式
//     cout << func([](int x){return x * 4;}, 2) << endl;
//     return 0;
// }

// int main() {
//     // 函数指针
//     function<int(int)> f1 = f;
//     cout << func(f1, 2) << endl;
//     cout << "****************" << endl;

//     // 函数对象
//     function<int(int)> f2 = Functor();
//     cout << func(f2, 2) << endl;
//     cout << "****************" << endl;

//     // lambda表达式
//     function<int(int)> f3 = [](int x) {return x * 4;};
//     cout << func(f3, 2) << endl;
//     cout << "****************" << endl;

//     return 0;
// }
#include <vector>
#include <stack>
#include <string>
using namespace std;

// class Solution {
// public:
//     int evalRPN(vector<string>& tokens) {
//         stack<int> st;
//         for (auto& str : tokens) {
//             if (str == "+" || str == "-" || str == "*" || str == "/") {
//                 int right = st.top();
//                 st.pop();
//                 int left = st.top();
//                 st.pop();

//                 switch (str[0]) {
//                     case '+':
//                         st.push(left + right);
//                         break;
//                     case '-':
//                         st.push(left - right);
//                         break;
//                     case '*':
//                         st.push(left * right);
//                         break;
//                     case '/':
//                         st.push(left / right);
//                         break;
//                 }
//             } else {
//                 st.push(stoi(str));
//             }
//         }
//         return st.top();
//     }
// };
// simple(1)
// template<class Fn, class ...Args>
// /* unspecified */ bind (Fn&& fn, Args&&... args);

// with return type(2)
// template<class Ret, class Fn, class... Args
// /* unspecified */ bind (Fn&& fn, Args&&... args);


// #include <functional>
// #include <iostream>
// using namespace std;
// int Sub(int a, int b) {
//     return (a - b) * 10;
// }
// int main() {
//     // auto f1 = bind(Sub, placeholders::_1, placeholders::_2);
//     // cout << f1(10, 5) << endl;
//     auto f2 = bind(Sub, placeholders::_1, 2);
//     cout << f2(10) << endl;
//     return 0;
// }


// #include <iostream>
// #include <functional>
// using namespace std;
// class Foo {
// public:
//     void print(int val) const { 
//         std::cout << "Foo value: " << val << std::endl; 
//     }
// };

// int main() {
//     Foo obj;
//     function<void(int)> func_binder = bind(&Foo::print, &obj, placeholders::_1);
//     // function<void(int)> func_binder = bind(&Foo::print, obj, placeholders::_1); // 也可以传入对象
//     func_binder(42); 
//     return 0;
// }

// #include <iostream>
// #include <functional>

// int main() {
//     using namespace std::placeholders;
//     auto lambda_add = [](int a, int b) { 
//         return a + b; 
//     };
//     auto lambda_reorder = std::bind(lambda_add, _2, _1);
//     std::cout << "Reordered sum: " << lambda_reorder(10, 20) << std::endl; 
//     return 0;
// }

#include <iostream>
#include <functional>
using namespace std;
class Add {
    public:
        int add(int x, int y) {
            return x * 10 + y;
        }
};

int main() {
    function<int(int, int)> f = bind(&Add::add, Add(), placeholders::_2, placeholders::_1);
    cout << f(1, 2) << endl;
    return 0;
}